/**
 * 第一步：引入（require）
 */
// 配置路径引入的方式
const path = require('path')
const DataHub = require('macaca-datahub');
const datahubMiddleware = require('datahub-proxy-middleware');
const HTMLPlugin = require('html-webpack-plugin')
const webpack = require('webpack')
const VueLoaderPlugin = require('vue-loader/lib/plugin.js')
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
/**
 * 第二步：定义变量
 */
// 1、设置环境，启动时环境变量是存储在process.env对象里面的
const isDev = process.env.NODE_ENV === 'development'
// 2、定义loader存放的数组
const webpackLoaders = []

// 3、定义插件数组存放Plugin
const webpackPlugins = []

// 4、全局变量(loader、plugin)
webpackLoaders.push(
  // 打包.vue文件
  {
    test: /\.vue$/,
    // 可以自定义配置将vue的css提取到单独的文件
    loader: 'vue-loader'
  },

  // 打包样式资源
  // {
  //   test: /\.css$/,
  //   use: [
  //     'style-loader',
  //     'css-loader'
  //   ]
  // },

  // 打包图片资源
  {
    test: /\.(png|jpg|jpeg|gif|svg)$/,
    use: [
      // 使用对象的方式来配置loader
      {
        // 将图片转成base64，图片小于1024时，大于时使用file-loader处理
        loader: 'url-loader',
        options: {
          limit: 1024,
          name: 'images/[name]-todo.[ext]',
          esModule: false //不让使用es语法
        }
      }
    ]
  },
)

webpackPlugins.push(
  // 为了方便在js代码和编译的过程中判断当前的环境
  new webpack.DefinePlugin({
    'process.dev': {
      NODE_ENV: isDev ? '"development"' : '"production"'
    }
  })
)

/**
 * 第三步：基本信息配置
 */

 // 1、不同的环境区分配置
 if(isDev){
  // 开发环境
  webpackLoaders.push(
    // css预处理器,处理顺序从下往上执行loader
    {
      test: /\.scss$/,
      use: [ 
        'style-loader', // 将 JS 字符串生成为 style 节点
        'css-loader', // 将 CSS 转化成 CommonJS 模块
        'postcss-loader',// 例如解决各个浏览的适配问题
        'sass-loader', // 将 Sass 编译成 CSS
        // 这个加载器将@import您的SASS资源放入每个requiredSASS模块中。因此，您可以在所有SASS样式中使用共享变量和mixin，而无需在每个文件中手动导入它们。使用CSS模块
        {
          loader: 'sass-resources-loader',
          options: {
            resources: [
              './src/assets/css/global/mixins.scss', 
              './src/assets/css/global/vars.scss' 
            ]
          }
        }
      ]
    }
  )
  webpackPlugins.push(
    new HTMLPlugin({
      template:'./index.html'
    }),
    new VueLoaderPlugin()
  )
 }else{
   webpackLoaders.push(
    {
      test: /\.scss$/,
      use: [
        {
          loader: MiniCssExtractPlugin.loader, 
          options: {
              /*
               * 在为css文件配置 loader时， 添加 publicPath 属性。 这样做， 我们在图片打包时， 
               * 仍会将图片复制在 /dist/images/ 文件夹之下， 但是 在css文件中引用时， 会将路径替换为 publicPath + name
               */
              publicPath: './'
          }
        },
        {
          loader: 'css-loader'
        },
        {
          loader: 'postcss-loader',// 例如解决各个浏览的适配问题
        },
        {
          loader: 'sass-loader'
        },
        // 全局引入sass文件
        {
          loader: 'sass-resources-loader',
          options: {
            resources: [
              './src/assets/css/global/mixins.scss', 
              './src/assets/css/global/vars.scss' 
            ]
          }
        }
      ]
    }
   )
   // 正式环境
   webpackPlugins.push(
    new MiniCssExtractPlugin({
      filename: "[name].css",
      chunkFilename: "[id].css"
    }),
    new HTMLPlugin({
      template:'./index.html'
    }),
    new VueLoaderPlugin(),
   )
 }

const config = {
  mode: 'development',
  // 1、入口
  entry: path.join(__dirname, 'src/index.js'),
  // 2、出口
  output: {
    // 输出的文件名
    filename: isDev ? 'bundle.[hash:8].js' : '[name].[chunkhash:8].js',
    // 输出的文件路径
    path: path.join(__dirname, 'dist')
  },
  // Webpack alias 配置
  resolve:{
    // 通过别名来把原导入路径映射成一个新的导入路径
    alias:{
      '@': path.join(__dirname, 'src')
    }
  },
  // 翻译官loader
  module: {
    rules: webpackLoaders
  },

  // 插件
  plugins: webpackPlugins
}

/**
  * datahub配置
  */

const datahubConfig = {
  port: 5678,
  hostname:'127.0.0.1',
  store: path.join(__dirname, 'data'),
  proxy: {
    '/api': {
      hub: 'todo'
    },
  },
  showBoard: false,
};

const defaultDatahub = new DataHub({
  // datahub的端口
  port: datahubConfig.port,
});

if(isDev){
  console.log(
    `\x1B[31m[请确认] \u001b[32m正在打包，当前打包环境: \u001b[33m${
      process.env.NODE_ENV
    }`
  );

  config.devServer = {
    //before方法：能够在其他所有的中间件之前执行自定义的中间件
    before: app => {
      datahubMiddleware(app)(datahubConfig);
    },

    //after方法：
    after: () => {
      defaultDatahub.startServer(datahubConfig).then(() => {
        console.log('datahub ready');
      });
    },
  }
}

module.exports = config